package staff.logic;

import static staff.logic.Employee.EMPLOYE_HEADER;

import java.io.PrintStream;
import java.util.Collections;
import java.util.Comparator;
import java.util.Iterator;
import java.util.LinkedList;
import java.util.List;

import staff.io.EmployeLoader;
import staff.io.EmployeSaver;

/** Class for employe management */
public class EmployeSystem implements Iterable<Employee> {
    /** List for holds all employe */
    private List<Employee> employeList = new LinkedList<Employee>();

    /** Adding employe to system */
    public void add(Employee employe) {
        if (employe == null) {
            throw new IllegalArgumentException("Illegal employe value: null.");
        }
        if (employeList.contains(employe)) {
            throw new IllegalStateException("There is employe with same ID in system.");
        }
        employeList.add(employe);
    }

    /** Get employe by id */
    public Employee get(int employeId) {
        for (Employee current : employeList) {
            if (current.getEmployeId() == employeId) {
                return current;
            }
        }
        throw new IllegalArgumentException("Employe not found in system. Employe id: " + employeId);
    }

    /** Remove employe from system */
    public boolean remove(Employee employe) {
        if (employe == null) {
            throw new IllegalArgumentException("Illegal employe value: null");
        }
        return employeList.remove(employe);
    }

    /** Remove employe from system by id */
    public boolean remove(int employeId) {
        Employee employe = get(employeId);
        return remove(employe);
    }

    /** Iterator for employe system */
    public Iterator<Employee> iterator() {
        return employeList.iterator();
    }

    /** Sort employe by id - default sorting order */
    public void sort() {
        Collections.sort(employeList);
    }

    /** Sort employe with comparator */
    public void sort(Comparator<Employee> employeComparator) {
        Collections.sort(employeList, employeComparator);
    }

    /** Load employes */
    public void load(EmployeLoader employeLoader) {
        try {
            while (employeLoader.hasNext()) {
                add(employeLoader.loadNext());
            }
        } finally {
            employeLoader.close();
        }
    }

    /** Save employes */
    public void save(EmployeSaver employeSaver) {
        try {
            for (Employee current : employeList) {
                employeSaver.saveNext(current);
            }
        } finally {
            employeSaver.close();
        }
    }

    /** Print employe list to print stream */
    public void print(PrintStream printStream) {
        printStream.println(EMPLOYE_HEADER);
        for (Employee current : employeList) {
            printStream.println(current);
        }
    }

    /** Clear employe system */
    public void clear() {
        employeList.clear();
    }

}
